package com.sj.purchase.modules.cost.service.stock;

import com.sj.purchase.manager.SkuInfo;
import com.sj.purchase.manager.SkuInfoManager;
import com.sj.purchase.modules.cost.domain.order.InOrder;
import com.sj.purchase.modules.cost.domain.price.SkuAvgPriceId;
import com.sj.purchase.modules.cost.repository.order.InOrderRepository;
import com.sj.purchase.modules.cost.repository.order.SkuAvgPriceRepository;
import com.sj.purchase.modules.cost.views.stock.InStockDetailsVO;
import com.sj.purchase.modules.cost.views.stock.OutStockDetailsVO;
import com.sj.purchase.modules.cost.views.stock.StockDetailsVO;
import com.sj.purchase.common.utils.mapper.BeanMapper;
import com.sj.purchase.modules.cost.domain.imei.Imei;
import com.sj.purchase.modules.cost.domain.order.OutOrder;
import com.sj.purchase.modules.cost.domain.price.SkuAvgPrice;
import com.sj.purchase.modules.cost.repository.imei.ImeiRepository;
import com.sj.purchase.modules.cost.repository.order.OutOrderRepository;
import org.apache.commons.lang3.tuple.Pair;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import org.springframework.web.bind.annotation.RequestParam;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;

/**
 * 库存明细
 * Created by yangrd on 2017/7/27.
 */
@Service
public class StockDetailsService {

    @Autowired
    private ImeiRepository imeiRepository;

    @Autowired
    private InOrderRepository inOrderRepository;


    @Autowired
    private OutOrderRepository outOrderRepository;

    @Autowired
    private SkuInfoManager skuInfoManager;

    @Autowired
    private SkuAvgPriceRepository skuAvgPriceRepository;

    /**
     * 库存信息和总条目数
     */
    public Pair<List<StockDetailsVO>, Long> getStockDetailsAndTotal(Date day, String sku, Pageable pageable) {
        Page<Imei> imeiPage = imeiRepository.findByDayAndSku(day, sku, pageable);
        List<StockDetailsVO> content = imeiPage.getContent().stream().map(this::buildInStockDetailsVO).map(this::conversion).collect(Collectors.toList());
        return Pair.of(content, imeiPage.getTotalElements());
    }

    /**
     * 入库信息和总条目数
     */
    public Pair<List<InStockDetailsVO>, Long> getInStockDetailsAndTotal(Date day, String orderNo, String sku, String imei, Pageable pageable) {
        if (Objects.isNull(imei)) {
            //入库单号 spu+日期
            Page<Imei> imeiPage = imeiRepository.findInImeiByCreateDateAndOrderNoAndSku(day, orderNo, sku, pageable);
            List<InStockDetailsVO> content = imeiPage.getContent().stream().map(this::buildInStockDetailsVO).collect(Collectors.toList());
            return Pair.of(content, imeiPage.getTotalElements());
        } else {
            //imei
            Imei imei1 = imeiRepository.findByIdImeiAndAndImeiType(imei, Imei.ImeiType.IN);
            List<InStockDetailsVO> content = Objects.nonNull(imei1) ? asList(buildInStockDetailsVO(imei1)) : null;
            return Pair.of(content, 1L);
        }
    }


    /**
     * 出库信息和总条目数
     */
    public Pair<List<OutStockDetailsVO>, Long> getOutStockDetailsAndTotal(Date day, String sku, @RequestParam(required = false) String imei, Pageable pageable) {
        if (Objects.isNull(imei)) {
            //spu+日期
            Page<Imei> imeiPage = imeiRepository.findOutImeiByByCreateDateAndSku(day, sku, pageable);
            List<OutStockDetailsVO> content = imeiPage.getContent().stream().map(this::buildOutStockDetailsVO).collect(Collectors.toList());
            return Pair.of(content, imeiPage.getTotalElements());
        } else {
            //imei
            Imei imei1 = imeiRepository.findByIdImeiAndAndImeiType(imei, Imei.ImeiType.OUT);
            List<OutStockDetailsVO> content = Objects.nonNull(imei1) ? asList(buildOutStockDetailsVO(imei1)) : null;
            return Pair.of(content, 1L);
        }
    }

    private StockDetailsVO conversion(InStockDetailsVO inStockDetailsVO) {
        StockDetailsVO stockDetailsVO = BeanMapper.map(inStockDetailsVO, StockDetailsVO.class);
        SkuAvgPrice skuAvgPriceEntity = skuAvgPriceRepository.findOne(new SkuAvgPriceId().setSkuNo(inStockDetailsVO.getImei()).setDay(inStockDetailsVO.getDay()));
        Double skuAvgPrice = skuAvgPriceEntity != null ? skuAvgPriceEntity.getPrice() : 0D;
        return stockDetailsVO.setAvePrice(skuAvgPrice).setImeiPrice(inStockDetailsVO.getPrice());
    }

    private InStockDetailsVO buildInStockDetailsVO(Imei imei) {
        InOrder inOrder = inOrderRepository.findFirstByOrderNo(imei.getId().getOrderNo());
        String warehouse = inOrder != null ? inOrder.getWarehouseEnum().getName() : null;
        //TODO
        Double price =  0D;
        SkuInfo skuInfo = skuInfoManager.getSkuInfo(imei.getSku());
        return InStockDetailsVO.instance().setDarwin(skuInfo.getDarwin()).setSpuNo(skuInfo.getSpucode()).setSkuNo(imei.getSku()).setSkuName(skuInfo.getSkuname()).setImei(imei.getId().getImei())
                .setDay(imei.getCreateDate()).setWarehouse(warehouse).setOrderNo(imei.getId().getOrderNo()).setPrice(price);
    }

    //之所以没有重用入库是因为有可能出现调库的情况还有价格会不同
    private OutStockDetailsVO buildOutStockDetailsVO(Imei imei) {
        OutOrder outOrder = outOrderRepository.findFirstByOrderNo(imei.getId().getOrderNo());
        String warehouse = outOrder != null ? outOrder.getWarehouseEnum().getName() : null;
        //TODO
        Double price = 0D;
        SkuInfo skuInfo = skuInfoManager.getSkuInfo(imei.getSku());
        return OutStockDetailsVO.instance().setDarwin(skuInfo.getDarwin()).setSpuNo(skuInfo.getSpucode()).setSkuNo(imei.getSku()).setSkuName(skuInfo.getSkuname()).setImei(imei.getId().getImei())
                .setDay(imei.getCreateDate()).setWarehouse(warehouse).setOrderNo(imei.getId().getOrderNo()).setPrice(price);
    }

    private <T> List<T> asList(T... ts) {
        List<T> list = new ArrayList<>();
        for (T t : ts) {
            list.add(t);
        }
        return list;
    }

}
